package com.quan.server.helper;

import com.mark.util.JsonUtil;
import com.quan.server.Const;
import com.taobao.api.ApiException;
import com.taobao.api.DefaultTaobaoClient;
import com.taobao.api.TaobaoClient;
import com.taobao.api.request.TbkAdzoneCreateRequest;
import com.taobao.api.request.TbkCouponGetRequest;
import com.taobao.api.request.TbkItemInfoGetRequest;
import com.taobao.api.request.TbkTpwdCreateRequest;
import com.taobao.api.request.WirelessShareTpwdCreateRequest;
import com.taobao.api.request.WirelessShareTpwdQueryRequest;
import com.taobao.api.response.TbkAdzoneCreateResponse;
import com.taobao.api.response.TbkCouponGetResponse;
import com.taobao.api.response.TbkItemInfoGetResponse;
import com.taobao.api.response.TbkTpwdCreateResponse;
import com.taobao.api.response.WirelessShareTpwdCreateResponse;
import com.taobao.api.response.WirelessShareTpwdQueryResponse;
import org.apache.commons.lang3.StringUtils;
import org.glassfish.jersey.client.ClientProperties;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import org.springframework.beans.factory.annotation.Value;
import org.springframework.stereotype.Component;

import javax.ws.rs.client.Client;
import javax.ws.rs.client.ClientBuilder;
import javax.ws.rs.core.Response;
import java.io.BufferedReader;
import java.io.InputStreamReader;
import java.io.UnsupportedEncodingException;
import java.math.BigDecimal;
import java.net.HttpURLConnection;
import java.net.URL;
import java.net.URLEncoder;
import java.nio.charset.StandardCharsets;
import java.util.List;
import java.util.Map;

@Component
public class AlimamaClient {
    private static Logger logger = LoggerFactory.getLogger(AlimamaClient.class);

    @Value("${alimama.appkey}")
    public String alimamaAppkey;

    @Value("${alimama.secret}")
    public String alimamaSecret;

    @Value("${alimama.url}")
    public String alimamaUrl;

    @Value("${alimama.siteId}")
    public long alimamaSiteId;

    public String getQuan(String taoPassword, String alimamaPid) {
        return getQuan(taoPassword, alimamaPid, 40);
    }

    public String getQuan(String taoPassword, String alimamaPid, double rateFinalUser) {
        try {
            taoPassword = getTaoPasswordKey(taoPassword);
            logger.error("3----------------> taoPassword:{}, alimamaPid:{}, rateFinalUser:{}", taoPassword, alimamaPid, rateFinalUser);
            String productUrl = convertTaobaoTaoPassword2Url(taoPassword);
            logger.error("3.1----------------> convertTaobaoTaoPassword2Url:taoPassword:{}, productUrl:{}", taoPassword, productUrl);
            String itemId = getItemIdFromProductUrl(productUrl);
            logger.error("3.3----------------> getItemIdFromProductUrl:productUrl:{}, itemId:{}", productUrl, itemId);

            Map activityInfo = getActivityInfoFromZhangchongchong(itemId, alimamaPid);
            logger.error("4.1---------------->getActivityInfoFromZhangchongchong itemId:{}, alimamaPid:{}, activityInfo:{}", itemId, alimamaPid, JsonUtil.bean2Json(activityInfo));
            if (activityInfo == null) {
                String activityId = getActivityIdByItemId(itemId);
                logger.error("5.0----------------> getActivityIdByItemId:itemId:{}, activityId:{}", itemId, activityId);
                double activityMoney = 0;
                if (activityId != null) {
                    activityMoney = getActivityMoney(itemId, activityId);
                    logger.error("5.1----------------> getActivityMoney itemId:{}, activityId:{}, activityMoney:{}", itemId, activityId, activityMoney);
                }
                logger.error("5.2---------------->getActivityInfoFromZhangchongchong failed, using default ");
                Map info = getAlimamaInfoById(itemId);
                logger.error("5.3---------------->getAlimamaInfoById failed, using default ");
                if (info == null) {
                    return "获取优惠券信息失败，请稍后重试。";
                } else {
                    String includeDxjh = info.get("includeDxjh").toString();
                    logger.error("5.4---------------->includeDxjh:{}", includeDxjh);

                    String newTaoPasswordUrl = getNewTaoPasswordUrl(itemId, activityId, alimamaPid, includeDxjh);
                    logger.error("5.5---------------->getNewTaoPasswordUrl itemId:{}, activityId:{}, alimamaPid:{}, includeDxjh:{}, newTaoPasswordUrl:{}", itemId, activityId, alimamaPid, includeDxjh, newTaoPasswordUrl);
                    String newTaoPasswordCode = converAlimamatUrl2AlimamaTaoPassword(newTaoPasswordUrl);
                    logger.error("5.6---------------->converAlimamatUrl2AlimamaTaoPassword newTaoPasswordUrl:{}, newTaoPasswordCode:{}", newTaoPasswordUrl, newTaoPasswordCode);

                    double tkCommFee = Double.valueOf(info.get("tkCommFee").toString());
                    String title = info.get("title").toString();
                    double priceOriginal = Double.valueOf(info.get("zkPrice").toString());
                    double moneyQuan = activityMoney;
                    double priceActual = priceOriginal - activityMoney;
                    double moneyBack = tkCommFee * rateFinalUser / 100;
                    BigDecimal b = new BigDecimal(moneyBack);
                    moneyBack = b.setScale(2, BigDecimal.ROUND_HALF_UP).doubleValue();
                    logger.error("5.7---------------->title:{}, newTaoPasswordCode:{}, priceOriginal:{}, priceActual:{}, moneyQuan:{}, moneyBack:{}", title, newTaoPasswordCode, priceOriginal, priceActual, moneyQuan, moneyBack);
                    String newQuan = getOutputQuan(title, newTaoPasswordCode, priceOriginal, priceActual, moneyQuan, moneyBack);
                    return newQuan;
                }
            } else {
                Map info = getAlimamaInfoById(itemId);
                logger.error("6.1---------------->itemId:{}, info:{}", itemId, JsonUtil.bean2Json(info));
                String newAlimamaUrl = activityInfo.get("coupon_click_url").toString();
                String newTaoPasswordCode = converAlimamatUrl2AlimamaTaoPassword(newAlimamaUrl);
                double rate = Double.valueOf(activityInfo.get("max_commission_rate").toString());
                String activityMoneyString = StringUtils.substringBetween(activityInfo.get("coupon_info").toString(), "减", "元");
                double activityMoney = activityMoneyString != null ? Double.valueOf(activityMoneyString) : 0;
                String title = info.get("title").toString();
                double priceOriginal = Double.valueOf(info.get("zkPrice").toString());
                double moneyQuan = activityMoney;
                double priceActual = priceOriginal - activityMoney;
                double moneyBack = priceActual * rate / 100 * rateFinalUser / 100;
                BigDecimal b = new BigDecimal(moneyBack);
                moneyBack = b.setScale(2, BigDecimal.ROUND_HALF_UP).doubleValue();
                logger.error("6.2---------------->title:{}, newTaoPasswordCode:{}, priceOriginal:{}, priceActual:{}, moneyQuan:{}, moneyBack:{}", title, newTaoPasswordCode, priceOriginal, priceActual, moneyQuan, moneyBack);
                String newQuan = getOutputQuan(title, newTaoPasswordCode, priceOriginal, priceActual, moneyQuan, moneyBack);
                return newQuan;
            }
        } catch (Exception e) {
            logger.error("", e);
            return null;
        }
    }

    public static String getTaoPasswordKey(String taoPassword) {
        return StringUtils.substringBetween(taoPassword, "￥", "￥");
    }

    public double getActivityMoney(String itemId, String activityId) {
        try {
            TaobaoClient client = new DefaultTaobaoClient(this.alimamaUrl, this.alimamaAppkey, this.alimamaSecret);
            TbkCouponGetRequest req = new TbkCouponGetRequest();
            req.setItemId(Long.valueOf(itemId));
            req.setActivityId(activityId);
            TbkCouponGetResponse rsp = client.execute(req);
            System.out.println(JsonUtil.format(rsp.getBody()));
            return Double.valueOf(rsp.getData().getCouponAmount());
        } catch (ApiException e) {
            e.printStackTrace();
        }
        return 0;
    }

    public String convertTaobaoTaoPassword2Url(String taoPassword) {
        try {
            TaobaoClient client = new DefaultTaobaoClient(this.alimamaUrl, this.alimamaAppkey, this.alimamaSecret);
            WirelessShareTpwdQueryRequest req = new WirelessShareTpwdQueryRequest();
            req.setPasswordContent(taoPassword);
            WirelessShareTpwdQueryResponse rsp = client.execute(req);
            return rsp.getUrl();
        } catch (Exception e) {
            logger.error("", e);
            return null;
        }
    }

    public String convertTaobaoUrl2TaobaoTaoPassword(String taobaoUrl) {
        try {
            TaobaoClient client = new DefaultTaobaoClient(this.alimamaUrl, this.alimamaAppkey, this.alimamaSecret);
            WirelessShareTpwdCreateRequest req = new WirelessShareTpwdCreateRequest();
            WirelessShareTpwdCreateRequest.GenPwdIsvParamDto obj1 = new WirelessShareTpwdCreateRequest.GenPwdIsvParamDto();
            obj1.setUrl(taobaoUrl);
            obj1.setText("超值活动，惊喜活动多多");
            req.setTpwdParam(obj1);
            WirelessShareTpwdCreateResponse rsp = client.execute(req);
            return rsp.getModel();
        } catch (Exception e) {
            logger.error("", e);
            return null;
        }
    }

    public String converAlimamatUrl2AlimamaTaoPassword(String url) {

        try {
            TaobaoClient client = new DefaultTaobaoClient(this.alimamaUrl, this.alimamaAppkey, this.alimamaSecret);
            TbkTpwdCreateRequest req = new TbkTpwdCreateRequest();
            req.setText("购买商品 获得返利");
            req.setUrl(url);
            req.setLogo("https://uland.taobao.com/");
            req.setExt("{}");
            TbkTpwdCreateResponse rsp = client.execute(req);
            String model = rsp.getData().getModel();
            return model;
        } catch (Exception e) {
            logger.error("", e);
            return null;
        }
    }

    public static String getContentFromUrl(String url) {
        Client client = ClientBuilder.newClient();
        Response response = client.target(url)
            .property(ClientProperties.FOLLOW_REDIRECTS, Boolean.TRUE)
            .property("User-Agent", "Mozilla/5.0 (iPhone; CPU iPhone OS 6_1_3 like Mac OS X) AppleWebKit/536.26 (KHTML, like Gecko) Mobile/10B329 MicroMessenger/5.0.1")
            .request().get(Response.class);
        String content = response.readEntity(String.class);
        return content;
    }

    public static String getActivityIdByItemId(String id) {
        String quanAPIUrl = "http://quan.meiquan8.com/?mod=inc&act=plugin&do=quan&iid=" + id;
        String content = getContentFromUrl(quanAPIUrl);
        Map map = JsonUtil.json2Bean(content, Map.class);
        if ((int) map.get("s") > 0) {
            return map.get("r").toString();
        }
        return null;
    }

    private String getOutputQuan(String title, String taoPasswordCode, double priceOriginal, double priceActual, double moneyQuan, double moneyBack) {
        String outputQuan = String.format(Const.TemplateQuan, title, taoPasswordCode, priceOriginal, priceActual, moneyBack, moneyQuan);
        return outputQuan;
    }

    private String getNewTaoPasswordUrl(String id, String activityId, String alimamaPid, String includeDxjh) {
        activityId = (activityId == null) ? "" : activityId;
        String url = "https://uland.taobao.com/coupon/edetail?activityId=" + activityId + "&pid=" + alimamaPid + "&itemId=" + id + "&src=pgy_pgyqf&dx=" + includeDxjh;
        logger.error(url);
        return url;
    }

    public static String getItemIdFromProductUrl(String url) {
        //id在参数开始，中间，结尾，都有可能
        String id = StringUtils.substringBetween(url, "?id=", "&");
        if (id == null) {
            id = StringUtils.substringBetween(url, "&id=", "&");
        }
        if (id == null) {
            id = StringUtils.substringAfter(url, "&id=");
        }
        if (StringUtils.isNumeric(id)) {
            return id;
        } else {
            return null;
        }
    }

    public static Map getAlimamaInfoById(String itemId) {
        Map alimamaInfo = null;
        try {
            Map content = getItemInfoFromAlimama(itemId);
            logger.error("getAlimamaInfoById itemId:{}, result:{}", itemId, JsonUtil.bean2Json(content));
            List alimamaInfoList = (List) getMap(content, "data", "pageList");
            if (alimamaInfoList.size() > 0) {
                alimamaInfo = (Map) alimamaInfoList.get(0);
            }
        } catch (Exception e) {
            e.printStackTrace();
        }
        return alimamaInfo;
    }

    public static Object getMap(Map map, String... pathArray) {
        for (String path : pathArray) {
            Object object = map.get(path);
            if (object instanceof Map) {
                map = (Map) object;
            } else {
                return object;
            }
        }
        return map;
    }

    //    获取阿里妈妈的内容，如果商品同时有高佣金和低佣金，只能看到高佣金
    public static Map getItemInfoFromAlimama(String itemId) {
        try {
            String taobaoItemUrl = "https://item.taobao.com/item.htm?id=" + itemId;
            taobaoItemUrl = URLEncoder.encode(taobaoItemUrl, StandardCharsets.UTF_8.toString());
            String url = "http://pub.alimama.com/items/search.json?q=" + taobaoItemUrl;
            String content = getContentFromUrl(url);
            Map productInfo = JsonUtil.json2Bean(content, Map.class);
            return productInfo;
        } catch (Exception e) {
            logger.error("", e);
            return null;
        }
    }

    public String createPid(String adzoneInfo) {
        try {
            TaobaoClient client = new DefaultTaobaoClient(this.alimamaUrl, this.alimamaAppkey, this.alimamaSecret);
            TbkAdzoneCreateRequest req = new TbkAdzoneCreateRequest();
            req.setSiteId(this.alimamaSiteId);
            req.setAdzoneName(adzoneInfo);
            TbkAdzoneCreateResponse rsp = client.execute(req);
            return rsp.getData().getModel();
        } catch (Exception e) {
            logger.error("", e);
            return null;
        }
    }

    public Map getActivityInfoFromZhangchongchong(String itemId, String pid) {
        String token = "70002100608f167a89ae1247980698089eb20b984f2c674960194f42149abad2737dabf888483807";

        String[] array = pid.split("_");
        String adzoneId = array[3];
        String siteId = array[2];
        String qq = "2116177952";

        String url = "https://b.9xiaoma.com/app/public/HightApi.xiaocao?token=%s&item_id=%s&adzone_id=%s&site_id=%s&qq=%s";
        url = String.format(url, token, itemId, adzoneId, siteId, qq);

        String json = sendPOST(url);
        logger.error("getActivityInfoFromZhangchongchong===============>itemId:{}, pid:{}, result:{}", itemId, pid, JsonUtil.format(json));
        Map result = JsonUtil.json2Bean(json, Map.class);
        Map info = (Map) getMap(result, "result", "data");
        return info;
    }

    private static String sendPOST(String postUrl) {
        try {
            URL url = new URL(postUrl);
            HttpURLConnection httpURLConnection = (HttpURLConnection) url.openConnection();
            httpURLConnection.setRequestMethod("POST");
            int responseCode = httpURLConnection.getResponseCode();

            if (responseCode == HttpURLConnection.HTTP_OK) { //success
                BufferedReader bufferedReader = new BufferedReader(new InputStreamReader(
                    httpURLConnection.getInputStream()));
                String inputLine;
                StringBuffer buffer = new StringBuffer();

                while ((inputLine = bufferedReader.readLine()) != null) {
                    buffer.append(inputLine);
                }
                bufferedReader.close();

                return buffer.toString();
            } else {
                logger.error("POST request not worked, postUrl:" + postUrl);
                return null;
            }
        } catch (Exception e) {
            logger.error("", e);
            return null;
        }
    }

    public Map getItemInfo(String itemId) {
        try {
            TaobaoClient client = new DefaultTaobaoClient(this.alimamaUrl, this.alimamaAppkey, this.alimamaSecret);
            TbkItemInfoGetRequest req = new TbkItemInfoGetRequest();
            req.setFields("num_iid,title,pict_url,small_images,reserve_price,zk_final_price,user_type,provcity,item_url");
            req.setPlatform(1L);
            req.setNumIids(itemId);
            TbkItemInfoGetResponse rsp = client.execute(req);
            System.out.println(rsp.getBody());
            return null;
        } catch (Exception e) {
            logger.error("", e);
            return null;
        }
    }
}
